package com.hengyue.system.service.impl;

import com.hengyue.common.utils.StringUtils;
import com.hengyue.system.domain.entity.SysOperLog;
import com.hengyue.system.repository.SysOperLogRepository;
import com.hengyue.system.service.ISysOperLogService;
import jakarta.persistence.criteria.Predicate;
import lombok.RequiredArgsConstructor;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/**
 * 操作日志 服务层处理
 *
 * @author ruoyi
 */
@Service
@RequiredArgsConstructor
public class SysOperLogServiceImpl implements ISysOperLogService {


    private final SysOperLogRepository operLogRepository;

    /**
     * 新增操作日志
     *
     * @param operLog 操作日志对象
     */
    @Override
    public void insertOperlog(SysOperLog operLog) {
        operLogRepository.save(operLog);
    }

    /**
     * 查询系统操作日志集合
     *
     * @param operLog 操作日志对象
     * @return 操作日志集合
     */
    @Override
    public Page<SysOperLog> selectOperLogList(SysOperLog operLog, Pageable pageable) {

        Specification<SysOperLog> spec = (root, query, cb) -> {
            List<Predicate> predicates = new ArrayList<>();

            // IP地址模糊查询
            if (StringUtils.isNotEmpty(operLog.getOperIp())) {
                predicates.add(cb.like(root.get("operIp"), "%" + operLog.getOperIp() + "%"));
            }

            // 标题模糊查询
            if (StringUtils.isNotEmpty(operLog.getTitle())) {
                predicates.add(cb.like(root.get("title"), "%" + operLog.getTitle() + "%"));
            }

            // 业务类型精确查询
            if (operLog.getBusinessType() != null) {
                predicates.add(cb.equal(root.get("businessType"), operLog.getBusinessType()));
            }

            // 业务类型数组查询
            if (operLog.getBusinessTypes() != null && operLog.getBusinessTypes().length > 0) {
                predicates.add(root.get("businessType").in(Arrays.asList(operLog.getBusinessTypes())));
            }
            // 状态查询
            if (operLog.getStatus() != null) {
                predicates.add(cb.equal(root.get("status"), operLog.getStatus()));
            }
            // 操作人模糊查询
            if (StringUtils.isNotEmpty(operLog.getOperName())) {
                predicates.add(cb.like(root.get("operName"), "%" + operLog.getOperName() + "%"));
            }
            // 时间范围查询
            if (operLog.getParams() != null) {
                if (operLog.getParams().get("beginTime") != null) {
                    predicates.add(cb.greaterThanOrEqualTo(
                            root.get("operTime"),
                            operLog.getParams().get("beginTime")
                    ));
                }
                if (operLog.getParams().get("endTime") != null) {
                    predicates.add(cb.lessThanOrEqualTo(
                            root.get("operTime"),
                            operLog.getParams().get("endTime")
                    ));
                }
            }
            // 按操作ID降序排序
            query.orderBy(cb.desc(root.get("id")));

            return query.where(predicates.toArray(new Predicate[0])).getRestriction();
        };

        return operLogRepository.findAll(spec,pageable);
    }

    @Override
    public List<SysOperLog> selectOperLogList(SysOperLog operLog) {
        return operLogRepository.findAll();
    }


    /**
     * 批量删除系统操作日志
     *
     * @param operIds 需要删除的操作日志ID
     */
    @Override
    public void deleteOperLogByIds(List<Long> operIds) {
        operLogRepository.deleteAllByIdInBatch(operIds);
    }

    /**
     * 查询操作日志详细
     *
     * @param operId 操作ID
     * @return 操作日志对象
     */
    @Override
    public SysOperLog selectOperLogById(Long operId) {
        return operLogRepository.findById(operId).orElse(null);
    }

    /**
     * 清空操作日志
     */
    @Override
    public void cleanOperLog() {
        operLogRepository.deleteAllInBatch();
    }

}
